package com.hyh.admin.sys.controller.base;

import cn.hutool.core.util.RandomUtil;
import cn.hutool.json.JSON;
import cn.hutool.json.JSONUtil;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.hyh.ad.common.annotation.Log;
import com.hyh.ad.common.annotation.LoginLog;
import com.hyh.ad.common.constants.RedisConstant;
import com.hyh.ad.common.core.controller.BaseController;
import com.hyh.ad.common.core.domain.AjaxResult;
import com.hyh.ad.common.core.domain.login.LoginUser;
import com.hyh.ad.common.core.domain.model.LoginBody;
import com.hyh.ad.common.core.domain.model.SysRole;
import com.hyh.ad.common.core.domain.model.SysUser;
import com.hyh.ad.common.core.page.TableDataInfo;
import com.hyh.ad.common.core.redis.CacheClient;
import com.hyh.ad.common.enums.BusinessType;
import com.hyh.ad.common.utils.CheckCodeUtil;
import com.hyh.ad.common.utils.PhoneUtil;
import com.hyh.ad.common.utils.SecurityUtils;
import com.hyh.admin.sys.service.ISysUserService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.OutputStream;
import java.time.LocalDate;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.TimeUnit;

@Slf4j
@RequestMapping("/api/sysUser")
@RestController
@Api(tags = "系统用户管理")
public class SysUserController extends BaseController {

    @Autowired
    private ISysUserService sysUserService;

    @Autowired
    private CacheClient cacheClient;

    
    /**
     * 验证码
     * @param response
     */
    @ApiOperation(value = "生成验证码 --弃用 需要前端携带uuid唯一标识 不方便")
    @GetMapping("/generate")
    public void generateCaptcha(HttpServletResponse response, HttpServletRequest request) throws IOException {
        String UUID = request.getParameter("UUID");
        response.setContentType("image/jpeg");
        OutputStream fos = response.getOutputStream();
        String checkCode = CheckCodeUtil.outputVerifyImage(100, 50, fos, 4);
        log.info("验证码:{}", checkCode);
        cacheClient.setObject(RedisConstant.CAPTCHA_PREFIX + UUID, checkCode, RedisConstant.TIMEOUT_FIVE, TimeUnit.MINUTES);
    }


    /**
     * 登录操作
     * @param user
     * @return AjaxResult
     */
    @PostMapping("/login")
    @ApiOperation(value = "用户登录 --弃用 需要前端携带uuid唯一标识 不方便")
    public AjaxResult login(@RequestBody SysUser user) {
        return sysUserService.login(user);
    }

    /**
     * 用户名密码登录
     * @param loginBody
     * 对象参数包括以下字段：
     * 用户名 名字或者手机号
     * 密码
     * 验证码
     * uuid
     */
    @ApiOperation(value = "通过用户名密码登陆 ")
    @PostMapping("/loginByPwd")
    @LoginLog(businessName = "用户登录")
    public AjaxResult loginByPassword(@RequestBody LoginBody loginBody) {
        return sysUserService.loginByPassword(loginBody.getUsername(), loginBody.getPassword(), loginBody.getCode(), loginBody.getUuid());
    }

    /**
     * 通过手机号发送验证码
     * @param  phone
     * @return 发送信息的请求返回
     */
    @ApiOperation(value = "通过手机号发送验证码")
    @PostMapping("/sendCode")
    public AjaxResult sendCode(@RequestParam("phone") String phone) {
        String content = PhoneUtil.send(phone, RandomUtil.randomNumbers(6));
        //将content格式化为json字符串
        return AjaxResult.success(content);
    }

    /**
     * 注册操作
     * @param user
     * @return AjaxResult
     */
    @PostMapping("/register")
    @ApiOperation(value = "用户注册")
    @LoginLog(businessName = "用户注册")
    public AjaxResult register(@RequestBody SysUser user) {
        return sysUserService.register(user);
    }

    /**
     * 查询用户列表
     * @param  sysUser
     * @return TableDataInfo
     */
    @PreAuthorize("hasAnyAuthority('sys:admin:permission','sys:crud:user')")
    @GetMapping("/list")
    @ApiOperation(value = "查询用户列表")
    public TableDataInfo selectList(SysUser sysUser) {
        IPage<SysUser> sysUserIPage = sysUserService.selectBaseUserList(sysUser, createPage());
        return getPageDataToTable(sysUserIPage);
    }

    /**
     * 获取用户详细信息
     * @return AjaxResult
     */
    @GetMapping(value = "/detail")
    @ApiOperation(value = "获取用户详细信息")
    //@Log(businessName = BusinessType.OTHER, operationModule = "用户操作")
    public AjaxResult getInfo() {
        LoginUser loginUser = SecurityUtils.getLoginUser();
        log.info("user:{}", loginUser.getUser().getId());
        return AjaxResult.success(sysUserService.selectBaseUserById(loginUser.getUser().getId()));
    }

    /**
     * 获取一周内系统用户的访问数量
     * 存入redis当中
     * 一周一次更新
     * @param
     * @return
     */
    @GetMapping("/visit")
    @ApiOperation(value = "存入当日系统的访问数量")
    public AjaxResult getVisit() {

        return AjaxResult.success("开发中");
    }

    /**
     * 从redis当中获取访问量
     * @return 用户访问的数量集合
     */
    @GetMapping("/getVisit")
    @ApiOperation(value = "从redis当中获取一周的访问量")
    public AjaxResult getVisitFromRedis() {
        // 定义一周的天数
        String[] daysOfWeek = {"Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"};
        // 定义中文星期的对应
        String[] chineseDays = {"周一", "周二", "周三", "周四", "周五", "周六", "周日"};

        // 创建一个Map来存储每一天的访问量
        Map<String, Object> visitCounts = new HashMap<>();

        // 遍历每一天，从Redis中获取访问量
        for (int i = 0; i < daysOfWeek.length; i++) {
            String redisKey = RedisConstant.SYSTEM_VISIT_DAY + daysOfWeek[i]; // 根据星期几获取Redis键
            Object visitCount = cacheClient.getObject(redisKey); // 从Redis中获取访问量
            if (visitCount == null) {
                visitCount = 0; // 如果Redis中没有记录，设置为0
            }
            visitCounts.put(chineseDays[i], visitCount); // 使用中文星期作为Map的键
        }

        // 返回一周访问量集合
        return AjaxResult.success(visitCounts);
    }


    /**
     * 根据日期获取用户注册的数量
     * @param dateList
     * @return
     */
    @GetMapping("/getRegister")
    @ApiOperation(value = "根据日期获取用户注册的数量")
    @PreAuthorize("hasAnyAuthority('sys:admin:permission','sys:crud:user')")
    public AjaxResult getRegister(List<String> dateList) {
        //TODO 根据日期获取用户注册的数量
        return AjaxResult.success("开发中");
    }

    /**
     * 查询用户拥有哪些角色信息
     * @param id
     * @return
     */
    @GetMapping("/getRole")
    @ApiOperation(value = "查询用户拥有哪些角色信息")
    @PreAuthorize("hasAnyAuthority('sys:admin:permission','sys:crud:user')")
    public AjaxResult getRole(@RequestParam("userId") Long id) {
        List<SysRole> sysRoles = sysUserService.selectHasRoles(id);
        return AjaxResult.success(sysRoles);
    }
    /**
     * 更新用户账号状态
     * @param
     * @return
     */
    @PutMapping("/updateStatus")
    @ApiOperation(value = "更新用户账号状态")
    @PreAuthorize("hasAnyAuthority('sys:admin:permission','sys:crud:user')")
    public AjaxResult updateStatus(@RequestBody SysUser sysUser) {
        return toAjax(sysUserService.updateStatus(sysUser));
    }

    /**
     * 新增用户
     * @param sysUser
     * @return
     */
    @PostMapping("/add")
    @ApiOperation(value = "新增用户")
    @Log(businessName = BusinessType.INSERT, operationModule = "新增用户")
    @PreAuthorize("hasAnyAuthority('sys:admin:permission','sys:crud:user')")
    public AjaxResult add(@RequestBody SysUser sysUser) {
        return toAjax(sysUserService.insertSysUser(sysUser));
    }

    /**
     * 删除用户
     * @param  ids
     * @return
     */
    @DeleteMapping("/delete/{ids}")
    @ApiOperation(value = "删除用户")
    @Log(businessName = BusinessType.DELETE, operationModule = "删除用户")
    @PreAuthorize("hasAnyAuthority('sys:admin:permission','sys:crud:user')")
    public AjaxResult delete(@PathVariable Long[] ids) {
        return toAjax(sysUserService.deleteByIds(ids));
    }

    /**
     * 根据用户名查询用户
     * @param username
     */
    @GetMapping("/selectUserByUserName")
    @ApiOperation(value = "根据用户名查询用户")
    public AjaxResult selectUserByUserName(@RequestParam("username") String username) {
        return AjaxResult.success(sysUserService.selectUserByUserName(username));
    }

    /**
     * 用户信息补全
     * @param  sysUser
     * @return
     */
    @PostMapping("/complete")
    @ApiOperation(value = "用户信息补全")
    @Log(businessName = BusinessType.INSERT, operationModule = "信息补全")
    public AjaxResult complete(@RequestBody SysUser sysUser) {
        return toAjax(sysUserService.updateById(sysUser));
    }


    /*
     * 根据用户ID查询数据
     */
    @GetMapping("/get/{id}")
    @ApiOperation(value = "根据用户ID查询数据")
    public AjaxResult get(@PathVariable Long id) {
        return AjaxResult.success(sysUserService.selectById(id));
    }
}
